package com.rslai.commons.util;

import java.sql.Timestamp;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;

@SuppressWarnings("serial")
public class DateUtil extends Date {

    public DateUtil() {
        super();
    }

    /**
     * <p>根据指定格式格式化日期</p>
     *
     * @param date Date对象
     * @param pattern 指定日期格式
     * @return 格式化后的时间字符串
     */
    public static String dateToString(Date date, String pattern) {
        String strDateTime = null;
        SimpleDateFormat formater = new SimpleDateFormat(pattern);
        strDateTime = date == null ? null : formater.format(date);
        return strDateTime;
    }

    /**
     * <p>日期格式化成  yyyy-MM-dd</p>
     *
     * @param date Date对象
     * @return 返回 yyyy-MM-dd 格式时间字符串
     */
    public static String dateToString(Date date) {
        String _pattern = "yyyy-MM-dd";
        return date == null ? null : dateToString(date, _pattern);
    }

    /**
     * <p>日期格式化成  yyyy-MM-dd HH:mm:ss</p>
     *
     * @param date Date对象
     * @return 返回 yyyy-MM-dd HH:mm:ss 格式时间字符串
     */
    public static String dateTimeToString(Date date) {
        String _pattern = "yyyy-MM-dd HH:mm:ss";
        return date == null ? null : dateToString(date, _pattern);
    }

    /**
     * <p>日期格式化成  yyyy-MM-dd HH:mm:ss:SSS</p>
     *
     * @param date Date对象
     * @return 返回 yyyy-MM-dd HH:mm:ss:SSS 格式时间字符串
     */
    public static String dateStampToString(Date date) {
        String _pattern = "yyyy-MM-dd HH:mm:ss:SSS";
        return date == null ? null : dateToString(date, _pattern);
    }

    /**
     * <p>日期格式化成  yyyyMMddHHmmssSSS</p>
     *
     * @param date Date对象
     * @return 返回 yyyyMMddHHmmssSSS 格式时间字符串
     */
    public static String dateStampToStringNoSp(Date date) {
        String _pattern = "yyyyMMddHHmmssSSS";
        return date == null ? null : dateToString(date, _pattern);
    }

    /**
     * <p>日期格式化成 MM/dd HH:mm:ss</p>
     *
     * @param date Date对象
     * @return 返回 MM/dd HH:mm:ss 格式时间字符串
     */
    public static String communityDateToString(Date date) {
        SimpleDateFormat formater = new SimpleDateFormat("MM/dd HH:mm:ss");
        String strDateTime = date == null ? null : formater.format(date);
        return strDateTime;
    }

    /**
     * <p>将一定格式的时间字符串转为日期 Date</p>
     *
     * @param str 时间字符串
     * @param pattern 指定日期格式
     * @return 转后的 Date
     */
    public static Date stringToDate(String str, String pattern) {
        Date dateTime = null;
        try {
            if (str != null && !str.equals("")) {
                SimpleDateFormat formater = new SimpleDateFormat(pattern);
                dateTime = formater.parse(str);
            }
        } catch (Exception ex) {
        }
        return dateTime;
    }

    /**
     * <p>将一定格式的时间字符串转为日期 Date 。格式 yyyy-MM-dd</p>
     *
     * @param str 时间字符串 yyyy-MM-dd
     * @return 转后的 Date
     */
    public static Date stringToDate(String str) {
        String _pattern = "yyyy-MM-dd";
        return stringToDate(str, _pattern);
    }

    /**
     * <p>将一定格式的时间字符串转为日期 Date 。格式  yyyy-MM-dd HH:mm:ss</p>
     *
     * @param str 时间字符串 yyyy-MM-dd HH:mm:ss
     * @return 转后的 Date
     */
    public static Date stringToDateTime(String str) {
        String _pattern = "yyyy-MM-dd HH:mm:ss";
        return stringToDate(str, _pattern);
    }

    /**
     * <p>将一定格式的时间字符串转为时间</p>
     *
     * @param str 字符串
     * @return Timestamp
     */
    public static Timestamp stringToDateHMS(String str) {
        Timestamp time = null;
        time = Timestamp.valueOf(str);
        return time;
    }

    /**
     * <p>根据年、月、日生成 Date</p>
     *
     * @param year 年
     * @param month 月
     * @param day 日
     * @return 生成后的 Date
     */
    public static Date ymdToDate(int year, int month, int day) {
        Calendar calendar = Calendar.getInstance();
        calendar.set(year, month, day);
        return calendar.getTime();
    }

    /**
     * <p>得到指定日期年份的最后一毫秒</p>
     *
     * @param date Date对象
     * @return	得到指定日期年份的最后一毫秒
     */
    public static Date getMaxDateOfYear(Date date){
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.set(Calendar.MONTH,calendar.getActualMaximum(Calendar.MONTH));
        calendar.set(Calendar.DAY_OF_MONTH,calendar.getActualMaximum(Calendar.DAY_OF_MONTH));
        calendar.set(Calendar.HOUR_OF_DAY, calendar.getActualMaximum(Calendar.HOUR_OF_DAY));
        calendar.set(Calendar.MINUTE, calendar.getActualMaximum(Calendar.MINUTE));
        calendar.set(Calendar.SECOND, calendar.getActualMaximum(Calendar.SECOND));
        calendar.set(Calendar.MILLISECOND, calendar.getActualMaximum(Calendar.MILLISECOND));

        return calendar.getTime();
    }

    /**
     * <p>得到指定日期年份的第一毫秒</p>
     *
     * @param date Date对象
     * @return	得到指定日期年份的第一毫秒
     */
    public static Date getMinDateOfYear(Date date){
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.set(Calendar.MONTH,calendar.getActualMinimum(Calendar.MONTH));
        calendar.set(Calendar.DAY_OF_MONTH,calendar.getActualMinimum(Calendar.DAY_OF_MONTH));
        calendar.set(Calendar.HOUR_OF_DAY, calendar.getActualMinimum(Calendar.HOUR_OF_DAY));
        calendar.set(Calendar.MINUTE, calendar.getActualMinimum(Calendar.MINUTE));
        calendar.set(Calendar.SECOND, calendar.getActualMinimum(Calendar.SECOND));
        calendar.set(Calendar.MILLISECOND, calendar.getActualMinimum(Calendar.MILLISECOND));

        return calendar.getTime();
    }

    /**
     * <p>得到指定日期月份的最后一毫秒</p>
     *
     * @param date Date对象
     * @return	得到指定日期月份的最后一毫秒
     */
    public static Date getMaxDateOfMonth(Date date){
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.set(Calendar.DAY_OF_MONTH,calendar.getActualMaximum(Calendar.DAY_OF_MONTH));
        calendar.set(Calendar.HOUR_OF_DAY, calendar.getActualMaximum(Calendar.HOUR_OF_DAY));
        calendar.set(Calendar.MINUTE, calendar.getActualMaximum(Calendar.MINUTE));
        calendar.set(Calendar.SECOND, calendar.getActualMaximum(Calendar.SECOND));
        calendar.set(Calendar.MILLISECOND, calendar.getActualMaximum(Calendar.MILLISECOND));

        return calendar.getTime();
    }

    /**
     * <p>得到指定日期月份的第一毫秒</p>
     *
     * @param date Date对象
     * @return	得到指定日期月份的第一毫秒
     */
    public static Date getMinDateOfMonth(Date date){
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.set(Calendar.DAY_OF_MONTH,calendar.getActualMinimum(Calendar.DAY_OF_MONTH));
        calendar.set(Calendar.HOUR_OF_DAY, calendar.getActualMinimum(Calendar.HOUR_OF_DAY));
        calendar.set(Calendar.MINUTE, calendar.getActualMinimum(Calendar.MINUTE));
        calendar.set(Calendar.SECOND, calendar.getActualMinimum(Calendar.SECOND));
        calendar.set(Calendar.MILLISECOND, calendar.getActualMinimum(Calendar.MILLISECOND));

        return calendar.getTime();
    }

    /**
     * <p>得到指定日期当日的最后一毫秒</p>
     *
     * @param date Date对象
     * @return java.util.Date
     */
    public static Date getMaxDateOfDay(Date date) {
        if (date == null) {
            return null;
        } else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            calendar.set(Calendar.HOUR_OF_DAY, calendar.getActualMaximum(Calendar.HOUR_OF_DAY));
            calendar.set(Calendar.MINUTE, calendar.getActualMaximum(Calendar.MINUTE));
            calendar.set(Calendar.SECOND, calendar.getActualMaximum(Calendar.SECOND));
            calendar.set(Calendar.MILLISECOND, calendar.getActualMaximum(Calendar.MILLISECOND));
            return calendar.getTime();
        }
    }

    /**
     * <p>得到指定日期当日的第一毫秒</p>
     *
     * @param date Date对象
     * @return java.util.Date
     */
    public static Date getMinDateOfDay(Date date) {
        if (date == null) {
            return null;
        } else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            calendar.set(Calendar.HOUR_OF_DAY, calendar.getActualMinimum(Calendar.HOUR_OF_DAY));
            calendar.set(Calendar.MINUTE, calendar.getActualMinimum(Calendar.MINUTE));
            calendar.set(Calendar.SECOND, calendar.getActualMinimum(Calendar.SECOND));
            calendar.set(Calendar.MILLISECOND, calendar.getActualMinimum(Calendar.MILLISECOND));
            return calendar.getTime();
        }
    }

    /**
     * <p>得到指定日期当小时的最后一毫秒</p>
     *
     * @param date Date对象
     * @return java.util.Date
     */
    public static Date getMaxDateOfHour(Date date) {
        if (date == null) {
            return null;
        } else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            calendar.set(Calendar.MINUTE, calendar.getActualMaximum(Calendar.MINUTE));
            calendar.set(Calendar.SECOND, calendar.getActualMaximum(Calendar.SECOND));
            calendar.set(Calendar.MILLISECOND, calendar.getActualMaximum(Calendar.MILLISECOND));
            return calendar.getTime();
        }
    }

    /**
     * <p>得到指定日期当小时的第一毫秒</p>
     *
     * @param date Date对象
     * @return java.util.Date
     */
    public static Date getMinDateOfHour(Date date) {
        if (date == null) {
            return null;
        } else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            calendar.set(Calendar.MINUTE, calendar.getActualMinimum(Calendar.MINUTE));
            calendar.set(Calendar.SECOND, calendar.getActualMinimum(Calendar.SECOND));
            calendar.set(Calendar.MILLISECOND, calendar.getActualMinimum(Calendar.MILLISECOND));
            return calendar.getTime();
        }
    }

    /**
     * <p>得到指定日期当分钟的最后一毫秒</p>
     *
     * @param date Date对象
     * @return java.util.Date
     */
    public static Date getMaxDateOfMinute(Date date) {
        if (date == null) {
            return null;
        } else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            calendar.set(Calendar.SECOND, calendar.getActualMaximum(Calendar.SECOND));
            calendar.set(Calendar.MILLISECOND, calendar.getActualMaximum(Calendar.MILLISECOND));
            return calendar.getTime();
        }
    }

    /**
     * <p>得到指定日期当分钟的第一毫秒</p>
     *
     * @param date Date对象
     * @return java.util.Date
     */
    public static Date getMinDateOfMinute(Date date) {
        if (date == null) {
            return null;
        } else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            calendar.set(Calendar.SECOND, calendar.getActualMinimum(Calendar.SECOND));
            calendar.set(Calendar.MILLISECOND, calendar.getActualMinimum(Calendar.MILLISECOND));
            return calendar.getTime();
        }
    }

    /**
     * <p>取指定日后n天，n允许为负数</p>
     *
     * @param date Date对象
     * @param afterDays 指定后几天或前几天，正数为后几天，负数为前几天
     * @return java.util.Date
     */
    public static Date getAfterDay(Date date, int afterDays) {
        Calendar cal = Calendar.getInstance();
        cal.setTime(date);
        cal.add(Calendar.DATE, afterDays);
        return cal.getTime();
    }

    /**
     * <p>获取指定几个月后的日期，n允许为负数</p>
     *
     * @param date Date对象
     * @param afterMonth 指定后几个月或前几个月，正数为后几个月，负数为前几个月
     * @return java.util.Date
     */
    public static java.util.Date getAfterMonth( java.util.Date date, int afterMonth){
        GregorianCalendar cal = new GregorianCalendar();
        cal.setTime(date);
        cal.add(java.util.Calendar.MONTH,afterMonth);
        return cal.getTime();
    }

    /**
     * <p>计算两个时间之间的 天数</p>
     *
     * @param date1 Date对象1
     * @param date2 Date对象2
     * @return 相差的天数
     */
    public static int dateDiff(Date date1, Date date2) {
        int i = (int) ((date1.getTime() - date2.getTime()) / 3600 / 24 / 1000);
        return i;
    }

    /**
     * <p>计算两个时间中之间的 分钟数</p>
     *
     * @param date1 Date对象1
     * @param date2 Date对象2
     * @return 相差的分钟数
     */
    public static int minuteDiff(Date date1, Date date2) {
        int i = (int) ((date1.getTime() - date2.getTime()) / 1000 / 60);
        return i;
    }

    /**
     * <p>计算两个时间中之间的 秒数</p>
     *
     * @param date1 Date对象1
     * @param date2 Date对象2
     * @return 相差的秒数
     */
    public static int timeDiff(Date date1, Date date2) {
        int i = (int) ((date1.getTime() - date2.getTime()));
        return i;
    }

    /**
     * <p>根据日期获取星期数</p>
     *
     * @param date Date对象
     * @return 星期数的中文
     */
    public static String getDayOfWeek(Date date){
        Calendar c = Calendar.getInstance();
        String week = null;
        c.setTime(date);
        if(c.get(Calendar.DAY_OF_WEEK) == 1){
            week = "[周日]";
        }else if(c.get(Calendar.DAY_OF_WEEK) == 2){
            week = "[周一]";
        }else if(c.get(Calendar.DAY_OF_WEEK) == 3){
            week = "[周二]";
        } else if(c.get(Calendar.DAY_OF_WEEK) == 4){
            week = "[周三]";
        } else if(c.get(Calendar.DAY_OF_WEEK) == 5){
            week = "[周四]";
        } else if(c.get(Calendar.DAY_OF_WEEK) == 6){
            week = "[周五]";
        } else if(c.get(Calendar.DAY_OF_WEEK) == 7){
            week = "[周六]";
        } else {
            week = "";
        }
        return week;
    }

    /**
     * <p>得到当前系统年份</p>
     *
     * @return 年份字符串
     */
    public static String getNowYear() {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        sdf.setLenient(false);
        return sdf.format(new java.util.Date()).split("-")[0];
    }

    /**
     * <p>得到当前系统月份</p>
     *
     * @return 月份字符串
     */
    public static String getNowMonth() {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        sdf.setLenient(false);
        return sdf.format(new java.util.Date()).split("-")[1];
    }

    /**
     * <p>得到当前系统日</p>
     *
     * @return 日字符串
     */
    public static String getNowDate() {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        sdf.setLenient(false);
        return sdf.format(new java.util.Date()).split("-")[2].split(" ")[0];
    }
}
